package com.katesoft.scale4j.rttp.hibernate;

import com.hazelcast.core.IMap;
import com.hazelcast.core.IdGenerator;
import com.katesoft.scale4j.persistent.model.RevisionDomainEntity;
import com.katesoft.scale4j.persistent.model.unified.IBO;
import com.katesoft.scale4j.rttp.internal.RttpHazelcastBridgeAwareImpl;
import net.jcip.annotations.ThreadSafe;
import org.hibernate.HibernateException;
import org.hibernate.id.IncrementGenerator;

import java.io.Serializable;

import static com.katesoft.scale4j.rttp.internal.IRttpHazelcastRefs.ID_GENERATOR_MAP;

/**
 * This is almost the same implementation as {@link IncrementGenerator} but safe in cluster env.
 *
 * @author kate2007
 */
@ThreadSafe
public class ClusteredIncrementGenerator extends RttpHazelcastBridgeAwareImpl implements Serializable
{
    public long generate(IBO bo) throws HibernateException
    {
        String name = bo.getPersistentClass().getName();
        return nextForKey(name);
    }

    public long generate(RevisionDomainEntity revision)
    {
        String name = revision.getClass().getName();
        return nextForKey(name);
    }

    protected long nextForKey(String key)
    {
        IMap<Object, Object> map = bridge.getHazelcastInstance().getMap(ID_GENERATOR_MAP);
        IdGenerator idGenerator = bridge.getHazelcastInstance().getIdGenerator(key);
        //
        return (map.containsKey(key) ? (Long) map.get(key) : 0) + idGenerator.newId();
    }
}
